package ar.uba.fi.algo3.algoTank.model.tanques;

import java.util.Iterator;
import ar.uba.fi.algo3.algoTank.model.Objeto;
import ar.uba.fi.algo3.algoTank.model.Vector;
import ar.uba.fi.algo3.algoTank.model.armas.Arma;
import ar.uba.fi.algo3.algoTank.model.escenarios.Escenario;
import ar.uba.fi.algo3.algoTank.model.formas.Figura;
import ar.uba.fi.algo3.algoTank.model.interfaces.Movible;
import ar.uba.fi.algo3.algoTank.model.paredes.Pared;
import ar.uba.fi.algo3.algoTank.model.proyectiles.Proyectil;
import ar.uba.fi.algo3.algoTank.util.Constantes;

public abstract class Tanque extends Objeto implements Movible {

	private Arma arma;

	private float velocidad;

	private float velocidadDisparo;

	public Tanque(Figura forma) {
		super(forma);
		setResistencia(100);
		velocidad = 1;
		velocidadDisparo = 2;
	}

	public Arma getArma() {
		return arma;
	}

	public void setArma(Arma arma) {
		this.arma = arma;
	}

	public void setVelocidad(float velocidad) {
		this.velocidad = velocidad;
	}

	public void setVelocidadDisparo(float velocidadDisparo) {
		this.velocidadDisparo = velocidadDisparo;
	}

	public float getVelocidad() {
		return velocidad;
	}

	public float getVelocidadDisparo() {
		return velocidadDisparo;
	}

	public void disparar() {
		arma.disparar();
	}

	public void aumentarVelocidad(float cantidad) {
		velocidad = velocidad + cantidad;
	}

	public void aumentarVelocidadDisparo(float cantidad) {
		velocidadDisparo = velocidadDisparo + cantidad;
	}

	private void controlarSiHayColision(Enum<Constantes.direccion> direccion) {

		Escenario escenario = Escenario.getInstancia();
		Iterator<Objeto> miIterador = escenario.getListaObjetos().iterator();
		boolean hayColision = false;
		while (miIterador.hasNext() && !hayColision) {
			Objeto objeto = miIterador.next();
			hayColision = this.hayColision(objeto);
		}

		if ((!escenario.estaEnLosLimitesDelEscenario(this)) || hayColision) {
			// Mover Para El Otro Lado
			if (direccion.equals(Constantes.direccion.ARRIBA)) {
				getPosicion().sumarVector(new Vector(0, 1 * velocidad));
			}
			else if (direccion.equals(Constantes.direccion.ABAJO)) {
				getPosicion().sumarVector(new Vector(0, -1 * velocidad));
			}
			else if (direccion.equals(Constantes.direccion.DERECHA)) {
				getPosicion().sumarVector(new Vector(-1 * velocidad, 0));
			}
			else if (direccion.equals(Constantes.direccion.IZQUIERDA)) {
				getPosicion().sumarVector(new Vector(1 * velocidad, 0));
			}

		}

	}

	public void mover(Enum<Constantes.direccion> direccion) {

		setDireccion(direccion);

		if (direccion.equals(Constantes.direccion.ARRIBA)) {
			getPosicion().sumarVector(new Vector(0, -1 * velocidad));
			controlarSiHayColision(direccion);
		}
		else if (direccion.equals(Constantes.direccion.ABAJO)) {
			getPosicion().sumarVector(new Vector(0, 1 * velocidad));
			controlarSiHayColision(direccion);
		}
		else if (direccion.equals(Constantes.direccion.DERECHA)) {
			getPosicion().sumarVector(new Vector(1 * velocidad, 0));
			controlarSiHayColision(direccion);
		}
		else if (direccion.equals(Constantes.direccion.IZQUIERDA)) {
			getPosicion().sumarVector(new Vector(-1 * velocidad, 0));
			controlarSiHayColision(direccion);
		}

	}

	public boolean hayColision(Objeto objeto) {
		if (!this.equals(objeto)) {
			return getForma().hayInterseccion(objeto.getForma());
		}
		else {
			return false;
		}
	}

	public boolean hayColision(Pared pared) {
		if (hayColision((Objeto) pared)) {
			return true;
		}
		else {
			return false;
		}
	}

	public boolean hayColision(Tanque tanque) {
		if (hayColision((Objeto) tanque)) {
			return true;
		}
		else {
			return false;
		}
	}

	public boolean hayColision(Proyectil proyectil) {
		if (hayColision((Objeto) proyectil)) {
			colisionar(proyectil);
			return true;
		}
		else {
			return false;
		}
	}

	private void colisionar(Proyectil proyectil) {
		quitarResistencia(proyectil.getDanio(this));
		Escenario.getInstancia().quitarObjeto(proyectil);
	}
}
